from flask_login import current_user
from flask_restful import Resource, marshal_with, reqparse  # type: ignore
from controllers.errors.roles_errors import HTTPSysMenuNotFoundError, HTTPSysMenuParamError
from core.roles.role_check import check_perms
from libs.login import login_required
from models.role import SysMenuType
from controllers.console import api
from services.errors.roles import SysMenuNotFoundError, SysMenuParamError
from services.menu_service import SysMenuService
from werkzeug.exceptions import InternalServerError
from fields.roles.menu_fields_def import menu_fields,menu_list_fields

class MenusManangeApi(Resource):
    @login_required
    @check_perms(perms=["menus:list"])
    @marshal_with(menu_list_fields)
    def get(self):
        parser = reqparse.RequestParser()
        parser.add_argument("id",type=str,required=False,location='args')
        parser.add_argument("parent_id",type=str,required=False,location='args')
        parser.add_argument("name",type=str,required=False,location='args')
        parser.add_argument("menu_type",type=str,required=False,location='args')
        parser.add_argument("page",type=int,required=False,location='args')
        parser.add_argument("page_size",type=int,required=False,location='args')
        args = parser.parse_args()
        menu_id = args.get("id")
        parent_id = args.get("parent_id")
        name = args.get("name")
        menu_type = args.get("menu_type")
        page = args.get("page",-1)
        page_size = args.get("page_size",-1)
        return SysMenuService.get_menu_list(current_user.current_tenant_id,menu_id,parent_id,name,menu_type,page,page_size)

    @login_required
    @check_perms(perms=["menus:new"])
    @marshal_with(menu_fields)
    def post(self):
        parser = reqparse.RequestParser()
        parser.add_argument("parent_id",type=str,required=False,location='json')
        parser.add_argument("name",type=str,required=True,location='json')
        parser.add_argument("url",type=str,required=False,location='json')
        parser.add_argument("menu_type",type=str,required=True,choices=SysMenuType.choices(),location='' \
        'json')
        parser.add_argument("perms",type=str,required=False,location='json')
        parser.add_argument("icon",type=str,required=False,location='json')
        parser.add_argument("component",type=str,required=False,location='json')
        # parser.add_argument("icon_url",type=str,required=False,location='json')
        parser.add_argument("seq",type=int,required=False,location='json')
        args = parser.parse_args()
        try:
            return SysMenuService.create_menu(current_user,args)
        except SysMenuNotFoundError as e:
            raise HTTPSysMenuNotFoundError(e.menu_id)
        except SysMenuParamError as e:
            raise HTTPSysMenuParamError(e.description)
        except Exception as e:
            raise InternalServerError(str(e))

    @login_required
    @check_perms(perms=["menus:update"])
    @marshal_with(menu_fields)
    def put(self):
        parser = reqparse.RequestParser()
        parser.add_argument("id",type=str,required=False,location='json')
        parser.add_argument("parent_id",type=str,required=False,location='json')
        parser.add_argument("name",type=str,required=True,location='json')
        parser.add_argument("url",type=str,required=False,location='json')
        parser.add_argument("menu_type",type=str,required=True,choices=SysMenuType.choices(),location='' \
        'json')
        parser.add_argument("perms",type=str,required=False,location='json')
        parser.add_argument("icon",type=str,required=False,location='json')
        parser.add_argument("component",type=str,required=False,location='json')
        # parser.add_argument("icon_url",type=str,required=False,location='json')
        parser.add_argument("seq",type=int,required=False,location='json')
        args = parser.parse_args()
        try:
            return SysMenuService.update_menu(current_user,args)
        except SysMenuNotFoundError as e:
            raise HTTPSysMenuNotFoundError(e.menu_id)
        except SysMenuParamError as e:
            raise HTTPSysMenuParamError(e.description)
        except Exception as e:
            raise InternalServerError(str(e))
        
    @login_required
    @check_perms(perms=["menus:del"])
    @marshal_with(menu_fields)
    def delete(self):
        parser = reqparse.RequestParser()
        parser.add_argument("id",type=str,required=False,location='args')
        args = parser.parse_args()
        menu_id = args.get("id")
        try:
            return SysMenuService.delete_menu(current_user.current_tenant_id,menu_id)
        except SysMenuNotFoundError as e:
            raise HTTPSysMenuNotFoundError(e.menu_id)
        except SysMenuParamError as e:
            raise HTTPSysMenuParamError(e.description)
        except Exception as e:
            raise InternalServerError(str(e))

api.add_resource(MenusManangeApi, '/menus')